home *** CD-ROM | disk | FTP | other *** search
/ Amiga Tools 5 / Amiga Tools 5.iso / grafik / 3d & render tools / irit / contrib / wavefrnt / irit2wf.c < prev    next >
Encoding:
C/C++ Source or Header  |  1996-07-16  |  6.7 KB  |  228 lines

  1. /*****************************************************************************
  2. * programm that parses IRIT data files and output it in WaveFront .obj         *
  3. * file format.                                     *
  4. *                                         *
  5. * Written by:  Gershon Elber                Ver 1.0, Feb 1993    *
  6. * Changed by:  Kariv Michael                Ver 1.0, Aug 1993    *
  7. *****************************************************************************/
  8.  
  9. #ifdef USE_VARARGS
  10. #include <varargs.h>
  11. #else
  12. #include <stdarg.h>
  13. #endif /* USE_VARARGS */
  14. #include <stdio.h>
  15. /* #include <stdlib.h>  */
  16. #include <math.h>
  17. #include <string.h>
  18. #include <time.h>
  19. #include "irit_sm.h"
  20. #include "iritprsr.h"
  21. #include "attribut.h"
  22. #include "getarg.h"
  23. #include "genmat.h"
  24. #include "ffcnvrt.h"
  25.  
  26. static MatrixType CrntViewMat;            /* This is the current view! */
  27. static int GlblFineNess = 10;
  28.  
  29. /* ADDED */
  30.  
  31. static int GlblVertices = 0;
  32.  
  33. static void PrintData(IPObjectStruct *PObj, int Indent);
  34. static char *Real2Str(RealType R);
  35.  
  36. /*****************************************************************************
  37. * Main routine - Read Parameter    line and do what you need...             *
  38. *****************************************************************************/
  39. void main(int argc, char **argv)
  40. {
  41.     IPObjectStruct *PObjects, *PObj;
  42.  
  43.     /* Get the data files: */
  44.     IritPrsrSetPolyListCirc(FALSE);
  45.     IritPrsrSetFlattenObjects(TRUE);
  46.  
  47.     if (argc == 1) {
  48.     char
  49.         *TmpStr = "-";
  50.  
  51.     PObjects = IritPrsrGetDataFiles(&TmpStr, 1, TRUE, FALSE);
  52.     }
  53.     else
  54.     PObjects = IritPrsrGetDataFiles(argv + 1, argc - 1, TRUE, FALSE);
  55.  
  56.     if (IritPrsrWasPrspMat)
  57.         MatMultTwo4by4(CrntViewMat, IritPrsrViewMat, IritPrsrPrspMat);
  58.     else
  59.     GEN_COPY(CrntViewMat, IritPrsrViewMat, sizeof(MatrixType));
  60.  
  61.     FFCState.LinearOnePolyFlag = TRUE;
  62.     FFCState.FourPerFlat = TRUE;
  63.     FFCState.OptimalPolygons = 0;
  64.     FFCState.FineNess = 10;
  65.     FFCState.OptimalPolylines = 0;
  66.     FFCState.SamplesPerCurve = 64;
  67.     FFCState.DrawFFMesh = FALSE;
  68.     FFCState.CubicCrvsAprox = FALSE;
  69.     FFCState.Talkative = TRUE;
  70.     FFCState.ShowInternal = FALSE;
  71.     FFCState.DrawFFGeom = TRUE;
  72.     FFCState.DumpObjsAsPolylines = FALSE;
  73.  
  74.     for (PObj = PObjects; PObj != NULL; PObj = PObj -> Pnext) {
  75.     if (IP_IS_FFGEOM_OBJ(PObj))
  76.         ProcessFreeForm(PObj, &FFCState);
  77.  
  78.     PrintData(PObj, 4);
  79.     }
  80. }
  81.  
  82. /*****************************************************************************
  83. * Routine to print the data from given geometry object.                 *
  84. *****************************************************************************/
  85. static void PrintData(IPObjectStruct *PObj, int Indent)
  86. {
  87.     int i, ii, j, NVertices, NNormals;
  88.     char
  89.     *ErrStr = NULL;
  90.     CagdRType *Coords;
  91.     IPPolygonStruct *PPolygon;
  92.     IPVertexStruct *PVertex;
  93.     IPAttributeStruct
  94.     *Attr = PObj -> Attrs;
  95.     IPVertexStruct *Vertices[100000];
  96.  
  97.     if (Attr != NULL) {
  98.     printf("\n");
  99.     while (Attr) {
  100.         printf("%s", Attr2String(Attr));
  101.         Attr = AttrTraceAttributes(Attr, NULL);
  102.     }
  103.     printf("\n");
  104.     }
  105.     
  106.     printf("g  %s\n", strlen(PObj -> Name) ? PObj -> Name : "default");
  107.  
  108.     Indent += 4;
  109.     
  110.     switch (PObj -> ObjType) {
  111.     case IP_OBJ_POLY:
  112.         NVertices = 0;
  113.         for (PPolygon = PObj -> U.Pl;
  114.          PPolygon != NULL;
  115.          PPolygon = PPolygon -> Pnext) {
  116.         if (PPolygon -> PVertex== NULL) {
  117.             fprintf(stderr,"Dump: Attemp to dump empty polygon\n");
  118.             exit(1);
  119.         }
  120.         PVertex = PPolygon -> PVertex;
  121.         do {             /* Assume at least one edge in polygon! */
  122.             for (ii =0; ii < NVertices; ii++)
  123.                 if (PVertex -> Coord[0] == Vertices[ii] -> Coord[0] &&
  124.                 PVertex -> Coord[1] == Vertices[ii] -> Coord[1] &&
  125.                 PVertex -> Coord[2] == Vertices[ii] -> Coord[2] &&
  126.                 PVertex -> Normal[0] == Vertices[ii] -> Normal[0] &&
  127.                 PVertex -> Normal[1] == Vertices[ii] -> Normal[1] &&
  128.                 PVertex -> Normal[2] == Vertices[ii] -> Normal[2])
  129.                 break;   /* This vertex isn't new in the object. */
  130.  
  131.             if (ii == NVertices) {
  132.             /* This vertex is new in the object. */
  133.             Vertices[ii] = PVertex;
  134.             NVertices ++;
  135.             printf("v  %s %s %s\n",
  136.                    Real2Str(PVertex -> Coord[0]),
  137.                    Real2Str(PVertex -> Coord[1]),
  138.                    Real2Str(PVertex -> Coord[2]));
  139.             printf("vn  %s %s %s\n",
  140.                    Real2Str(PVertex -> Normal[0]),
  141.                    Real2Str(PVertex -> Normal[1]),
  142.                    Real2Str(PVertex -> Normal[2]));
  143.             }
  144.  
  145.             PVertex = PVertex -> Pnext;
  146.         }
  147.         while (PVertex != PPolygon -> PVertex && PVertex != NULL);
  148.         }
  149.  
  150.         /* All vertices information was already printed.            */
  151.         /* Now faces (or polygons in the IRIT jargon) are printed.      */
  152.         printf("\n\n");
  153.  
  154.         printf("g  %s\n",
  155.              strlen(PObj -> Name) ? PObj -> Name : "default");
  156.         for (PPolygon = PObj -> U.Pl;
  157.          PPolygon != NULL;
  158.          PPolygon = PPolygon -> Pnext) {
  159.         printf("f  ");
  160.         PVertex = PPolygon -> PVertex;
  161.         do {
  162.             for (ii =0; ii < NVertices; ii++)
  163.                 if (PVertex -> Coord[0] == Vertices[ii] -> Coord[0] &&
  164.                 PVertex -> Coord[1] == Vertices[ii] -> Coord[1] &&
  165.                 PVertex -> Coord[2] == Vertices[ii] -> Coord[2] &&
  166.                 PVertex -> Normal[0] == Vertices[ii] -> Normal[0] &&
  167.                 PVertex -> Normal[1] == Vertices[ii] -> Normal[1] &&
  168.                 PVertex -> Normal[2] == Vertices[ii] -> Normal[2]) {
  169.                 /* +1 is because in .obj files the  */
  170.                 /* vertex numeration is from one.  */
  171.                 printf ("%d//%d ", GlblVertices + ii + 1,
  172.                                GlblVertices + ii + 1);
  173.                 break;
  174.             }
  175.  
  176.             if (ii == NVertices) {
  177.             printf("irit2wf: error");
  178.             exit(1);
  179.             }
  180.  
  181.             PVertex = PVertex -> Pnext;
  182.         } 
  183.         while (PVertex != PPolygon -> PVertex && PVertex != NULL);
  184.         printf("\n");
  185.         }
  186.         GlblVertices += NVertices;
  187.         break;
  188.     default:
  189.         fprintf(stderr,
  190.             "Dump: Attemp to dump undefine object \"%s\" type (%d).\n",
  191.             PObj -> Name ? PObj -> Name : "", PObj -> ObjType);
  192.         break;
  193.     }
  194.  
  195.     Indent -= 4;
  196. }
  197.  
  198. /*****************************************************************************
  199. * Convert a real number into a string.                         *
  200. * The routine maintains 6 different buffers simultanuously so up to 6 calls  *
  201. * can be issued from same printf...                         *
  202. *****************************************************************************/
  203. static char *Real2Str(RealType R)
  204. {
  205.     static int j, k,
  206.     i = 0;
  207.     static char Buffer[6][LINE_LEN_SHORT], Line[LINE_LEN];
  208.  
  209.     if (ABS(R) < EPSILON) R = 0.0;        /* Round off very small numbers. */
  210.  
  211.     sprintf(Buffer[i], "%6lg", R);
  212.  
  213.     for (k = 0; !isdigit(Buffer[i][k]) && k < LINE_LEN; k++);
  214.     if (k >= LINE_LEN) {
  215.     fprintf(stderr, "Conversion of real number (%f) failed.\n", R);
  216.     exit(1);
  217.     }
  218.  
  219.     for (j = strlen(Buffer[i]) - 1; Buffer[i][j] == ' ' && j > k; j--);
  220.     if (strchr(Buffer[i], '.') != NULL)
  221.     for (; Buffer[i][j] == '0' && j > k; j--);
  222.     Buffer[i][j+1] = 0;
  223.  
  224.     j = i;
  225.     i = (i + 1) % 6;
  226.     return Buffer[j];
  227. }
  228.